From 0cecf315fd766748d2510a9f0af4820c260c9aca Mon Sep 17 00:00:00 2001 From: Benjamin Otte Date: Mon, 17 Sep 2012 17:00:02 +0200 Subject: [PATCH] cssanimation: Implement pausing the animation --- gtk/gtkcssanimation.c | 53 ++++++++++++++++++++++++++++++------ gtk/gtkcssanimationprivate.h | 7 ++++- gtk/gtkcsscomputedvalues.c | 44 ++++++++++++++++++++---------- 3 files changed, 79 insertions(+), 25 deletions(-) diff --git a/gtk/gtkcssanimation.c b/gtk/gtkcssanimation.c index e4c692a19c..2ebf5858cf 100644 --- a/gtk/gtkcssanimation.c +++ b/gtk/gtkcssanimation.c @@ -27,18 +27,22 @@ G_DEFINE_TYPE (GtkCssAnimation, _gtk_css_animation, GTK_TYPE_STYLE_ANIMATION) +/* NB: Return value can be negative (if animation hasn't started yet) */ +static gint64 +gtk_css_animation_get_elapsed (GtkCssAnimation *animation, + gint64 for_time_us) +{ + if (animation->play_state == GTK_CSS_PLAY_STATE_PAUSED) + return animation->timestamp; + else + return for_time_us - animation->timestamp; +} /* NB: Return value can be negative and +-Inf */ static double gtk_css_animation_get_iteration (GtkCssAnimation *animation, gint64 for_time_us) { - gint64 elapsed; - double iterations; - - elapsed = for_time_us - animation->timestamp; - iterations = (double) elapsed / animation->duration; - - return iterations; + return (double) gtk_css_animation_get_elapsed (animation, for_time_us) / animation->duration; } static gboolean @@ -144,6 +148,9 @@ gtk_css_animation_is_static (GtkStyleAnimation *style_animation, GtkCssAnimation *animation = GTK_CSS_ANIMATION (style_animation); double iteration; + if (animation->play_state == GTK_CSS_PLAY_STATE_PAUSED) + return TRUE; + iteration = gtk_css_animation_get_iteration (animation, at_time_us); return iteration >= animation->iteration_count; @@ -182,7 +189,8 @@ _gtk_css_animation_init (GtkCssAnimation *animation) GtkStyleAnimation * _gtk_css_animation_new (const char *name, GtkCssKeyframes *keyframes, - gint64 start_time_us, + gint64 timestamp, + gint64 delay_us, gint64 duration_us, GtkCssValue *ease, GtkCssDirection direction, @@ -201,7 +209,11 @@ _gtk_css_animation_new (const char *name, animation->name = g_strdup (name); animation->keyframes = _gtk_css_keyframes_ref (keyframes); - animation->timestamp = start_time_us; + if (play_state == GTK_CSS_PLAY_STATE_PAUSED) + animation->timestamp = - delay_us; + else + animation->timestamp = timestamp + delay_us; + animation->duration = duration_us; animation->ease = _gtk_css_value_ref (ease); animation->direction = direction; @@ -219,3 +231,26 @@ _gtk_css_animation_get_name (GtkCssAnimation *animation) return animation->name; } + +GtkStyleAnimation * +_gtk_css_animation_copy (GtkCssAnimation *animation, + gint64 at_time_us, + GtkCssPlayState play_state) +{ + g_return_val_if_fail (GTK_IS_CSS_ANIMATION (animation), NULL); + + if (animation->play_state == play_state) + return g_object_ref (animation); + + return _gtk_css_animation_new (animation->name, + animation->keyframes, + at_time_us, + - gtk_css_animation_get_elapsed (animation, at_time_us), + animation->duration, + animation->ease, + animation->direction, + play_state, + animation->fill_mode, + animation->iteration_count); +} + diff --git a/gtk/gtkcssanimationprivate.h b/gtk/gtkcssanimationprivate.h index f992605c39..08dc663ca6 100644 --- a/gtk/gtkcssanimationprivate.h +++ b/gtk/gtkcssanimationprivate.h @@ -60,7 +60,8 @@ GType _gtk_css_animation_get_type (void) G_GNUC_CONST; GtkStyleAnimation * _gtk_css_animation_new (const char *name, GtkCssKeyframes *keyframes, - gint64 start_time_us, + gint64 timestamp, + gint64 delay_us, gint64 duration_us, GtkCssValue *ease, GtkCssDirection direction, @@ -68,6 +69,10 @@ GtkStyleAnimation * _gtk_css_animation_new (const char * GtkCssFillMode fill_mode, double iteration_count); +GtkStyleAnimation * _gtk_css_animation_copy (GtkCssAnimation *animation, + gint64 at_time_us, + GtkCssPlayState play_state); + const char * _gtk_css_animation_get_name (GtkCssAnimation *animation); G_END_DECLS diff --git a/gtk/gtkcsscomputedvalues.c b/gtk/gtkcsscomputedvalues.c index cd2f66b2d6..250b0b0d29 100644 --- a/gtk/gtkcsscomputedvalues.c +++ b/gtk/gtkcsscomputedvalues.c @@ -434,6 +434,7 @@ gtk_css_computed_values_find_animation (GtkCssComputedValues *values, static void gtk_css_computed_values_create_css_animations (GtkCssComputedValues *values, gint64 timestamp, + GtkCssComputedValues *source, GtkStyleContext *context) { GtkStyleProviderPrivate *provider; @@ -465,21 +466,34 @@ gtk_css_computed_values_create_css_animations (GtkCssComputedValues *values, if (animation) continue; - keyframes = _gtk_style_provider_private_get_keyframes (provider, name); - if (keyframes == NULL) - continue; + if (source) + animation = gtk_css_computed_values_find_animation (source, name); - keyframes = _gtk_css_keyframes_compute (keyframes, context); - - animation = _gtk_css_animation_new (name, - keyframes, - timestamp + _gtk_css_number_value_get (_gtk_css_array_value_get_nth (delays, i), 100) * G_USEC_PER_SEC, - _gtk_css_number_value_get (_gtk_css_array_value_get_nth (durations, i), 100) * G_USEC_PER_SEC, - _gtk_css_array_value_get_nth (timing_functions, i), - _gtk_css_direction_value_get (_gtk_css_array_value_get_nth (directions, i)), - _gtk_css_play_state_value_get (_gtk_css_array_value_get_nth (play_states, i)), - _gtk_css_fill_mode_value_get (_gtk_css_array_value_get_nth (fill_modes, i)), - _gtk_css_number_value_get (_gtk_css_array_value_get_nth (iteration_counts, i), 100)); + if (animation) + { + animation = _gtk_css_animation_copy (GTK_CSS_ANIMATION (animation), + timestamp, + _gtk_css_play_state_value_get (_gtk_css_array_value_get_nth (play_states, i))); + } + else + { + keyframes = _gtk_style_provider_private_get_keyframes (provider, name); + if (keyframes == NULL) + continue; + + keyframes = _gtk_css_keyframes_compute (keyframes, context); + + animation = _gtk_css_animation_new (name, + keyframes, + timestamp, + _gtk_css_number_value_get (_gtk_css_array_value_get_nth (delays, i), 100) * G_USEC_PER_SEC, + _gtk_css_number_value_get (_gtk_css_array_value_get_nth (durations, i), 100) * G_USEC_PER_SEC, + _gtk_css_array_value_get_nth (timing_functions, i), + _gtk_css_direction_value_get (_gtk_css_array_value_get_nth (directions, i)), + _gtk_css_play_state_value_get (_gtk_css_array_value_get_nth (play_states, i)), + _gtk_css_fill_mode_value_get (_gtk_css_array_value_get_nth (fill_modes, i)), + _gtk_css_number_value_get (_gtk_css_array_value_get_nth (iteration_counts, i), 100)); + } values->animations = g_slist_prepend (values->animations, animation); } } @@ -494,7 +508,7 @@ _gtk_css_computed_values_create_animations (GtkCssComputedValues *values, { if (source != NULL) gtk_css_computed_values_create_css_transitions (values, timestamp, source); - gtk_css_computed_values_create_css_animations (values, timestamp, context); + gtk_css_computed_values_create_css_animations (values, timestamp, source, context); } GtkBitmask * -- 2.30.2